package com.tank.client.handler;

import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.CopyOnWriteArrayList;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.tank.entity.Brick;
import com.tank.entity.Bullet;
import com.tank.entity.GameResource;
import com.tank.entity.Iron;
import com.tank.entity.Tank;
import com.tank.entity.Water;
import com.tank.map.Map;
import com.tank.response.CreateBulletResponse;
import com.tank.response.DestroyBrickResponse;
import com.tank.response.DestroyTankResponse;
import com.tank.response.InitialMapResponse;
import com.tank.response.PongResponse;
import com.tank.response.TankIdResponse;
import com.tank.response.TankLocationResponse;
import com.tank.view.TankPanel;
import com.tank.view.controller.TankController;
import com.tank.view.thread.BulletRepaintThread;
import com.tank.view.thread.RepaintThread;

import io.netty.channel.ChannelHandlerAdapter;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelPromise;
import io.netty.handler.timeout.IdleState;
import io.netty.handler.timeout.IdleStateEvent;

public class NettyClientHandler extends ChannelHandlerAdapter {

	private int heartbeatCount = 0;
	// 关闭链路后发起重连的间隔
	private final int INTERVAL = 5;
	// 心跳计数器能达到的最大值
	private final int MAX_HEARTBEAT_COUNT = 5;
	private static Logger log = LoggerFactory.getLogger(NettyClientHandler.class);

	@Override
	public void channelActive(ChannelHandlerContext ctx) {
		// System.out.println(ctx.channel().remoteAddress().toString());
	}

	@Override
	public void userEventTriggered(ChannelHandlerContext ctx, Object evt) throws Exception {

		if (evt instanceof IdleStateEvent) {
			IdleStateEvent e = (IdleStateEvent) evt;
			if (e.state() == IdleState.READER_IDLE) {

			}
		}
	}

	@Override
	public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {
		if (msg instanceof TankIdResponse) {
			TankIdResponse response = (TankIdResponse) msg;
			TankController.tankId = response.getTankId();
//			log.info("Receive-->tankId分配:tankId:" + response.getTankId());
		} else if (msg instanceof InitialMapResponse) {
//			log.info("Receive-->地图初始化消息");
			InitialMapResponse response = (InitialMapResponse) msg;
			GameResource resource = new GameResource();
			CopyOnWriteArrayList<Brick> bricks = new CopyOnWriteArrayList<>(response.getBricks());
			CopyOnWriteArrayList<Water> waters = new CopyOnWriteArrayList<>(response.getWaters());
			CopyOnWriteArrayList<Iron> irons = new CopyOnWriteArrayList<>(response.getIrons());
			ConcurrentHashMap<String, Tank> playerTanks = new ConcurrentHashMap<>(response.getPlayerTanks());
			Map map = new Map();
			map.setBricks(bricks);
			map.setWaters(waters);
			map.setIrons(irons);
			resource.setMap(map);
			resource.setPlayerTanks(playerTanks);
			TankPanel.resource = resource;
			Thread thread = new Thread(new RepaintThread(TankController.panel));
			thread.start();
		} else if (msg instanceof TankLocationResponse) {
			TankLocationResponse response = (TankLocationResponse) msg;
			Tank tank = TankPanel.resource.getPlayerTanks().get(response.getTankId());
			tank.setX(response.getX());
			tank.setY(response.getY());
			tank.setDirect(response.getDirect());
//				+ response.getY() + ")" + "坦克方向为" + response.getDirect());
		} else if (msg instanceof CreateBulletResponse) {
			CreateBulletResponse response = (CreateBulletResponse) msg;
			Bullet bullet = TankPanel.resource.getPlayerTanks().get(response.getTankId()).shot();
			// tank.getBullets().add(bullet);
			Thread t = new Thread(new BulletRepaintThread(bullet));
			t.start();
		} else if (msg instanceof DestroyBrickResponse) {
			DestroyBrickResponse response = (DestroyBrickResponse) msg;
			CopyOnWriteArrayList<Brick> bricks = TankPanel.resource.getMap().getBricks();
			for (Brick brick : bricks) {
				if (brick.getX() == response.getX() && brick.getY() == response.getY()) {
					bricks.remove(brick);
				}
			}
		} else if (msg instanceof DestroyTankResponse) {
			DestroyTankResponse response=(DestroyTankResponse)msg;
			TankPanel.resource.getPlayerTanks().get(response.getTankId()).setAlive(false);
		} else if (msg instanceof PongResponse) {

		}

	}

	@Override
	public void channelReadComplete(ChannelHandlerContext ctx) throws Exception {
		ctx.flush();
	}

	@Override
	public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {
		cause.printStackTrace();
		ctx.close();
	}

	@Override
	public void close(ChannelHandlerContext ctx, ChannelPromise promise) throws Exception {
		super.close(ctx, promise);
		System.out.println("close");
	}

	@Override
	public void channelInactive(ChannelHandlerContext ctx) throws Exception {
		super.channelInactive(ctx);
		System.out.println("channelInactive");
	}
}